import 'dart:typed_data';

import 'package:dio/dio.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter_inappwebview/flutter_inappwebview.dart';
import 'package:get/get.dart';
import 'package:sinosheets/main_config.dart';
import 'package:sinosheets/utils/common_utils/log_util.dart';

import 'gb_webview_cache.dart';

class GBWebViewController extends GetxController {
  final String baseUrl;
  final GBWebViewCache _cache = GBWebViewCache();
  InAppWebViewController? webViewController;
  final RxBool isLoading = true.obs;
  final RxInt progress = 0.obs;
  final RxInt cacheSize = 0.obs;
  final RxInt cacheCount = 0.obs;

  GBWebViewController(this.baseUrl);

  @override
  void onInit() {
    super.onInit();
    _initWebView();
    _updateCacheInfo();
    _checkVersion();
  }

  Future<void> _initWebView() async {
    await _cache.init();
  }

  /// 检查版本号
  Future<void> _checkVersion() async {
    try {
      final dio = Dio();
      final response = await dio.get('${AppPrefix.h5Prefix}/version.json');
      if (response.statusCode == 200 && response.data != null) {
        final version = response.data['buildTime'] as String;
        await _cache.updateVersion(version);
      }
    } catch (e) {
      LogUtil.e('检查版本失败: $e');
    }
  }

  /// 更新缓存信息
  Future<void> _updateCacheInfo() async {
    final info = await _cache.getCacheInfo();
    cacheSize.value = info['size'] ?? 0;
    cacheCount.value = info['count'] ?? 0;
  }

  /// 获取缓存信息
  Future<Map<String, dynamic>> getCacheInfo() async {
    return await _cache.getCacheInfo();
  }

  /// 检查URL是否已缓存
  Future<bool> isUrlCached(String url) async {
    return await _cache.isCached(url);
  }

  /// 清除缓存
  Future<void> clearCache() async {
    await _cache.clearCache();
    await _updateCacheInfo();
  }

  void updateProgress(int value) {
    progress.value = value;
  }

  Future<WebResourceResponse?> handleResourceLoading(
    String url,
  ) async {
    if (baseUrl.contains("192.")) {
      return null;
    }

    String indexUrl = url;
    if (url.startsWith(baseUrl)) {
      indexUrl = '${AppPrefix.h5Prefix}/index.html';
    }
    if (!url.startsWith(AppPrefix.h5Prefix)) {
      return null;
    }

    try {
      if (url.startsWith(baseUrl)) {
        final cached = await _cache.loadFromCache(indexUrl);
        if (cached != null) {
          return WebResourceResponse(
            contentType: _getMimeType(indexUrl),
            contentEncoding: 'utf-8',
            statusCode: 200,
            reasonPhrase: "OK",
            data: cached,
            headers: {
              'Cache-Control': 'private, max-age=31536000',
              'Content-Type': _getMimeType(indexUrl),
            },
          );
        }
      } else {
        final cached = await _cache.loadFromCache(url);
        if (cached != null) {
          return WebResourceResponse(
            contentType: _getMimeType(url),
            contentEncoding: 'utf-8',
            statusCode: 200,
            reasonPhrase: "OK",
            data: cached,
            headers: {
              'Cache-Control': 'private, max-age=31536000',
              'Content-Type': _getMimeType(url),
            },
          );
        }
      }
    } catch (e) {
      LogUtil.e('资源加载失败: $e');
    }
    return null;
  }

  /// 创建WebView配置
  InAppWebViewGroupOptions get webViewOptions => InAppWebViewGroupOptions(
        crossPlatform: InAppWebViewOptions(
          useShouldOverrideUrlLoading: true,
          mediaPlaybackRequiresUserGesture: false,
          useOnLoadResource: true,
          cacheEnabled: true,
          clearCache: false,
          incognito: false,
          javaScriptEnabled: true,
        ),
        android: AndroidInAppWebViewOptions(
          useHybridComposition: true,
          mixedContentMode: AndroidMixedContentMode.MIXED_CONTENT_ALWAYS_ALLOW,
          safeBrowsingEnabled: false,
        ),
        ios: IOSInAppWebViewOptions(
          allowsInlineMediaPlayback: true,
          allowsBackForwardNavigationGestures: true,
        ),
      );

  /// 获取资源拦截器
  Future<WebResourceResponse?> interceptRequest(String url) async {
    if (baseUrl.contains("192.")) {
      return null;
    }
    String indexUrl = url;
    if (url.startsWith(baseUrl)) {
      indexUrl = '${AppPrefix.h5Prefix}/index.html';
    }
    if (!url.startsWith(AppPrefix.h5Prefix)) return null;
    if (url.startsWith("${AppPrefix.h5Prefix}/api/")) return null;

    try {
      if (url.startsWith(baseUrl)) {
        final cached = await _cache.loadFromCache(indexUrl);
        if (cached != null) {
          return WebResourceResponse(contentType: _getMimeType(indexUrl), contentEncoding: 'utf-8', statusCode: 200, reasonPhrase: "OK", data: cached, headers: {
            'Cache-Control': 'private, max-age=31536000',
            'Content-Type': _getMimeType(indexUrl),
          });
        }
      } else {
        final cached = await _cache.loadFromCache(url);
        if (cached != null) {
          return WebResourceResponse(contentType: _getMimeType(url), contentEncoding: 'utf-8', statusCode: 200, reasonPhrase: "OK", data: cached, headers: {
            'Cache-Control': 'private, max-age=31536000',
            'Content-Type': _getMimeType(url),
          });
        }
      }

      final response = await Dio().get<List<int>>(
        url,
        options: Options(
          responseType: ResponseType.bytes,
          followRedirects: true,
          validateStatus: (status) => true,
        ),
      );

      if (response.statusCode == 200 && response.data != null) {
        final bytes = Uint8List.fromList(response.data!);
        if (url.startsWith(baseUrl)) {
          await _cache.saveToCache(indexUrl, bytes);
          return WebResourceResponse(contentType: _getMimeType(indexUrl), contentEncoding: 'utf-8', statusCode: 200, reasonPhrase: "OK", data: bytes, headers: {
            'Cache-Control': 'private, max-age=31536000',
            'Content-Type': _getMimeType(indexUrl),
          });
        } else {
          await _cache.saveToCache(url, bytes);
          return WebResourceResponse(contentType: _getMimeType(url), contentEncoding: 'utf-8', statusCode: 200, reasonPhrase: "OK", data: bytes, headers: {
            'Cache-Control': 'private, max-age=31536000',
            'Content-Type': _getMimeType(url),
          });
        }
      }
    } catch (e) {
      LogUtil.e('资源拦截失败: $e');
    }
    return null;
  }

  /// 获取MIME类型
  String _getMimeType(String url) {
    final ext = url.split('.').last.toLowerCase();
    switch (ext) {
      case 'html':
        return 'text/html';
      case 'js':
        return 'application/javascript';
      case 'css':
        return 'text/css';
      case 'png':
        return 'image/png';
      case 'jpg':
      case 'jpeg':
        return 'image/jpeg';
      case 'gif':
        return 'image/gif';
      case 'svg':
        return 'image/svg+xml';
      case 'json':
        return 'application/json';
      case 'woff':
        return 'application/font-woff';
      case 'woff2':
        return 'application/font-woff2';
      case 'ttf':
        return 'application/font-ttf';
      case 'eot':
        return 'application/vnd.ms-fontobject';
      case 'otf':
        return 'application/font-otf';
      default:
        return 'application/octet-stream';
    }
  }

  @override
  void onClose() {
    webViewController = null;
    super.onClose();
  }
}
